﻿using Core;
using Core.Data;
using Core.Domain.Companys;
using System;
using System.Linq;
using System.Collections.Generic;
using Core.Caching;

namespace Services.Companys
{
    public partial class CompanyService :ICompanyService
    {
        #region Constants
        private const string COMPANY_PATTERN_KEY = "pattern.company.";
        private const string COMPANY_ID_KEY = "pattern.company.id-{0}";

        #endregion

        #region Fields

        private readonly IRepository<Company> _companyRepository;
        private readonly ICacheManager _cacheManager;

        #endregion

        #region Ctor

        /// <summary>
        /// Ctor
        /// </summary>
        public CompanyService(
            IRepository<Company> companyRepository,
            ICacheManager cacheManager
            )
        {
            this._companyRepository = companyRepository;
            this._cacheManager = cacheManager;
        }

        #endregion

        #region Method
        public virtual void DeleteCompany(Company entity)
        {
            if (entity == null)
                throw new ArgumentNullException("Company");

            entity.Deleted = true;

            _companyRepository.Update(entity);
            _cacheManager.List_Remove(COMPANY_PATTERN_KEY, entity);
            
        }

        public virtual void InsertCompany(Company entity)
        {
            if (entity == null)
                throw new ArgumentNullException("Company");
            
            _companyRepository.Insert(entity);
        }

        /// <summary>
        /// 更新公司实体内容
        /// </summary>
        /// <param name="entity"></param>
        public virtual void UpdateCompany(Company entity)
        {
            if (entity == null)
                throw new ArgumentNullException("Company");

            _companyRepository.Update(entity);

            _cacheManager.List_Remove(COMPANY_PATTERN_KEY, entity);
        }

        /// <summary>
        /// 获取公司
        /// </summary>
        /// <param name="companyId"></param>
        /// <returns></returns>
        public virtual Company GetCompanyById(int companyId)
        {
            if (companyId == 0)
                return null;

            string key = string.Format(COMPANY_ID_KEY, companyId);

            return _cacheManager.Get(key, () => { return _companyRepository.GetById(companyId); });

        }

        public virtual IList<Company> GetCompanyByIds(int[] companyIds)
        {
            if (companyIds == null || companyIds.Length == 0)
                return new List<Company>();

            var query = from c in _companyRepository.Table
                        where companyIds.Contains(c.Id)
                        select c;
            var companys = query.ToList();

            var sortedCompanys = new List<Company>();
            foreach (int id in companyIds)
            {
                var company = companys.Find(x => x.Id == id);
                if (company != null)
                    sortedCompanys.Add(company);
            }
            return sortedCompanys;
        }

        public virtual IList<Company> GetCompanys(bool? active = true, bool? deleted = false)
        {
            var query = _companyRepository.Table;
            if (active.HasValue)
                query = query.Where(c => c.Active == active);

            if (deleted.HasValue)
                query = query.Where(c => c.Deleted == deleted);

            query = query.OrderBy(c => c.DisplayOrder);

            return query.ToList();
        }

        public virtual IPagedList<Company> GetCompanys(string name = "", string url = "", 
            int scaleId = 0, int cityId = 0,
            bool? active = true, bool? deleted = false,
            List<int> values=null,
            CompanySortingEnum sort = CompanySortingEnum.CreateDown, int pageIndex = 0, int pageSize = int.MaxValue)
        {
            var query = _companyRepository.Table;
            if (active.HasValue)
                query = query.Where(c => c.Active == active);

            if (deleted.HasValue)
                query = query.Where(c => c.Deleted == deleted);

            if (scaleId>0)
                query = query.Where(c => c.ScaleId == scaleId);

            if (cityId>0)
                query = query.Where(c => c.CityId == cityId);

            if (!String.IsNullOrWhiteSpace(name))
                query = query.Where(c => c.Name.Contains(name));

            if (!String.IsNullOrWhiteSpace(url))
                query = query.Where(c => c.URL.Contains(url));

            if (values != null && values.Count > 0)
                query = query.Where(x => x.CompanyAttribute.Any(e => values.Contains(e.ValueId)));
                
            if (sort == CompanySortingEnum.CreateDown)
                query = query.OrderBy(e => e.CreateOn);
            else
                query = query.OrderByDescending(e => e.CreateOn);

            return new PagedList<Company>(query, pageIndex, pageSize);

        }
        #endregion
    }
}
